package net.wy.commons.web.jacson;

import org.codehaus.jackson.map.SerializerFactory;
import org.codehaus.jackson.map.Serializers;
import org.codehaus.jackson.map.ser.BeanSerializerModifier;
import org.codehaus.jackson.map.util.ArrayBuilders;

/**
 * Created with IntelliJ IDEA.
 * User: Administrator
 * Date: 12-8-30
 * Time: 下午12:20
 * To change this template use File | Settings | File Templates.
 */
public class SimpleSerializerFactoryConfig extends SerializerFactory.Config {


    /**
     * Constant for empty <code>Serializers</code> array (which by definition
     * is stateless and reusable)
     */
    protected final static Serializers[] NO_SERIALIZERS = new Serializers[0];

    protected final static BeanSerializerModifier[] NO_MODIFIERS = new BeanSerializerModifier[0];

    /**
     * List of providers for additional serializers, checked before considering default
     * basic or bean serialializers.
     *
     * @since 1.7
     */
    protected final Serializers[] _additionalSerializers;

    /**
     * @since 1.8
     */
    protected final Serializers[] _additionalKeySerializers;

    /**
     * List of modifiers that can change the way {@link org.codehaus.jackson.map.ser.BeanSerializer} instances
     * are configured and constructed.
     */
    protected final BeanSerializerModifier[] _modifiers;

    public SimpleSerializerFactoryConfig() {
        this(null, null, null);
    }

    protected SimpleSerializerFactoryConfig(Serializers[] allAdditionalSerializers,
                         Serializers[] allAdditionalKeySerializers,
                         BeanSerializerModifier[] modifiers)
    {
        _additionalSerializers = (allAdditionalSerializers == null) ?
                NO_SERIALIZERS : allAdditionalSerializers;
        _additionalKeySerializers = (allAdditionalKeySerializers == null) ?
                NO_SERIALIZERS : allAdditionalKeySerializers;
        _modifiers = (modifiers == null) ? NO_MODIFIERS : modifiers;
    }

    @Override
    public SerializerFactory.Config withAdditionalSerializers(Serializers additional)
    {
        if (additional == null) {
            throw new IllegalArgumentException("Can not pass null Serializers");
        }
        Serializers[] all = ArrayBuilders.insertInListNoDup(_additionalSerializers, additional);
        return new SimpleSerializerFactoryConfig(all, _additionalKeySerializers, _modifiers);
    }

    @Override
    public SerializerFactory.Config withAdditionalKeySerializers(Serializers additional)
    {
        if (additional == null) {
            throw new IllegalArgumentException("Can not pass null Serializers");
        }
        Serializers[] all = ArrayBuilders.insertInListNoDup(_additionalKeySerializers, additional);
        return new SimpleSerializerFactoryConfig(_additionalSerializers, all, _modifiers);
    }

    @Override
    public SerializerFactory.Config withSerializerModifier(BeanSerializerModifier modifier)
    {
        if (modifier == null) {
            throw new IllegalArgumentException("Can not pass null modifier");
        }
        BeanSerializerModifier[] modifiers = ArrayBuilders.insertInListNoDup(_modifiers, modifier);
        return new SimpleSerializerFactoryConfig(_additionalSerializers, _additionalKeySerializers, modifiers);
    }

    @Override
    public boolean hasSerializers() { return _additionalSerializers.length > 0; }

    @Override
    public boolean hasKeySerializers() { return _additionalKeySerializers.length > 0; }

    @Override
    public boolean hasSerializerModifiers() { return _modifiers.length > 0; }

    @Override
    public Iterable<Serializers> serializers() {
        return ArrayBuilders.arrayAsIterable(_additionalSerializers);
    }

    @Override
    public Iterable<Serializers> keySerializers() {
        return ArrayBuilders.arrayAsIterable(_additionalKeySerializers);
    }

    @Override
    public Iterable<BeanSerializerModifier> serializerModifiers() {
        return ArrayBuilders.arrayAsIterable(_modifiers);
    }
}
